package com.filldream.fastboot.common.okutil.stock;

import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import com.filldream.fastboot.common.util.Assert;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.experimental.Accessors;
import java.math.BigDecimal;
import java.util.Date;

/**
 * 交易基础类
 * 交易佣金和印花税率
 */
@Data
@Accessors(chain = true)
public class TransactionBase {

    @ApiModelProperty(value = "证券公司佣金率，默认千分之0.854")
    private String commissionRate = "0.0000854";

    @ApiModelProperty(value = "印花税率，默认千分之0.5")
    private String flowerRate = "0.0005";

    @ApiModelProperty(value = "过户费,默认千分之0.01")
    private String transferRate = "0.00001";

    /**
     * 获取成交额 = 价格 * 数量
     * @return  成交额
     */
    public static String getAmount(String price,String number){
        return new BigDecimal(price).multiply(new BigDecimal(number+"")).toString();
    }

    /**
     * 获取佣金 = 成交额 * 佣金比例
     * @return  佣金
     */
    public static String getCommission(String price,String number){
        return new TransactionBase().getYj(new BigDecimal(getAmount(price,number))).toString();
    }

    /**
     * 获取过户费 = 成交额 * 过户费比例
     * @return  过户费
     */
    public static String getTransferFee(String price,String number){
        return new TransactionBase().getGhf(new BigDecimal(getAmount(price,number))).toString();
    }

    /**
     * 买入手续费 = 佣金 + 过户费
     * @return  买入手续费
     */
    public static String getBuyCommission(String price,String number){
        return new BigDecimal(getCommission(price,number)).add(new BigDecimal(getTransferFee(price,number))).toString();
    }

    /**
     * 买入成本 = 成交额 + 买入手续费
     * @return  买入成本
     */
    public static String getBuyCost(String price,String number){
        return new BigDecimal(getAmount(price,number)).add(new BigDecimal(getBuyCommission(price,number))).toString();
    }

    /**
     * 获取印花税 = 成交额 * 印花税比例
     * @return  印花税
     */
    public static String getTax(String price,String number){
        return new TransactionBase().getYhs(new BigDecimal(getAmount(price,number))).toString();
    }

    /**
     * 卖出手续费 = 佣金 + 过户费 + 印花税
     * @return  卖出手续费
     */
    public static String getSellCommission(String price,String number){
        return new BigDecimal(getCommission(price,number)).add(new BigDecimal(getTransferFee(price,number))).add(new BigDecimal(getTax(price,number))).toString();
    }

    /**
     * 卖出收益 = 成交额 - 卖出手续费
     * @return  卖出收益
     */
    public static String getProfit(String price,String number){
        return new BigDecimal(getAmount(price,number)).subtract(new BigDecimal(getSellCommission(price,number))).toString();
    }

    /**
     * 获取印花税
     * @param money 成交金额
     * @return  返回印花税金额
     */
    public  BigDecimal getYhs(BigDecimal money){
        return new BigDecimal(flowerRate).multiply(money);
    }

    /**
     * 获取佣金
     * 不足5元的按5元收费
     * @param price  成交金额
     * @return  返回佣金金额
     */
    public BigDecimal getYj(BigDecimal price){
        final BigDecimal money5 = new BigDecimal("5");
        BigDecimal yj = new BigDecimal(this.getCommissionRate()).multiply(price);
        return yj.compareTo(money5) <= 0 ? money5 : yj;
    }

    /**
     * 获取过户费
     * 不足0.1元的按0.1元收费
     * @param price  成交金额
     * @return
     */
    public BigDecimal getGhf(BigDecimal price){
        final BigDecimal defaultMoney = new BigDecimal("0.01");
        BigDecimal changeFee = new BigDecimal(this.getTransferRate()).multiply(price);
        return changeFee.compareTo(defaultMoney) <= 0 ? defaultMoney : changeFee;
    }

    /**
     * 校验交易数量是否为100的正整数倍
     * @param count
     */
    public static void check(String count){
        check(Integer.parseInt(count));
    }

    /**
     * 校验交易数量是否为100的正整数倍
     * @param count
     */
    public static void check(Integer count){
        Assert.isBoolean( !(count % 100 == 0), "交易数量必须为100的正整数倍" );
    }

    /**
     * 是否在阅读期间内
     * @return  返回boolean
     */
    public static boolean isInReadTime(){
        DateTime amStart = DateUtil.parse( "09:13:00",  "HH:mm:ss");
        DateTime amEnd = DateUtil.parse("11:31:00", "HH:mm:ss");
        DateTime pmStart = DateUtil.parse("12:59:00", "HH:mm:ss");
        DateTime pmEnd = DateUtil.parse("15:02:00", "HH:mm:ss");
        DateTime nowTime = DateUtil.parse(DateUtil.now().substring(11), "HH:mm:ss");
        return isInDay() && (DateUtil.isIn(nowTime, amStart, amEnd) || DateUtil.isIn(nowTime, pmStart, pmEnd));
    }

    /**
     * 是否在交易时间内
     * @return  返回boolean
     */
    public static boolean isInStockTime(){
        DateTime amStart = DateUtil.parse( "09:30:00",  "HH:mm:ss");
        DateTime amEnd = DateUtil.parse("11:30:00", "HH:mm:ss");
        DateTime pmStart = DateUtil.parse("13:00:00", "HH:mm:ss");
        DateTime pmEnd = DateUtil.parse("15:00:00", "HH:mm:ss");
        DateTime nowTime = DateUtil.parse(DateUtil.now().substring(11), "HH:mm:ss");
        // 判断当前时间是否在范围内
        return isInDay() && (DateUtil.isIn(nowTime, amStart, amEnd) || DateUtil.isIn(nowTime, pmStart, pmEnd));
    }

    /**
     * 是否在交易日
     * 周六周日一律为休市时间，不管是否是节假日
     * @return  返回boolean
     */
    public static boolean isInDay(){
        int day = DateUtil.dayOfWeek(new Date());
        return day != 1 && day != 7;
    }

    /**
     * 自动着色涨跌
     * @param price 价格
     * @param zf    涨幅
     * @return  涨幅正：红色 涨幅负：绿色 涨幅0：白色
     */
    public static String autoColorPrice(String price,String zf){
        return TransactionBase.autoColorPrice( price,new BigDecimal(zf).compareTo(BigDecimal.ZERO));
    }

    /**
     * 自动着色涨跌
     * @param price 价格
     * @param result    比较结果
     * @return  >0：红色 <0：绿色 =0：白色
     */
    public static String autoColorPrice(String price,int result){
        if(result > 0){
            return BaseUtil.getFormatOutputString(price,31,1,1);
        }else if( result < 0 ){
            return BaseUtil.getFormatOutputString(price,32,1,1);
        }else{
            return price;
        }
    }

    /**
     * 自动着色涨跌
     * @param price 价格
     * @param result    比较结果
     * @return  >0：红色 <0：绿色 =0：白色
     */
    public static String autoColorPrice(BigDecimal price, int result){
        return autoColorPrice(price.toString(),result);
    }
}
